package com.sl.au.service.impl;

import java.math.BigDecimal;
import java.text.ParseException;
import java.text.SimpleDateFormat;
import java.util.ArrayList;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.persistence.Query;

import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.data.domain.Page;
import org.springframework.data.domain.PageRequest;
import org.springframework.data.domain.Pageable;
import org.springframework.data.domain.Sort;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Propagation;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.util.StringUtils;

import com.sl.au.entity.AaccountsReceivableAccorspandingContract;
import com.sl.au.entity.ContractInfo;
import com.sl.au.entity.Customer;
import com.sl.au.entity.InvoiceDetailInfo;
import com.sl.au.entity.InvoiceTotalInfo;
import com.sl.au.entity.InvoiceTotalInfoFictitious;
import com.sl.au.entity.User;
import com.sl.au.repository.AaccountsReceivableAccorspandingContractRepository;
import com.sl.au.repository.ContractInfoRepository;
import com.sl.au.repository.CustomerRepository;
import com.sl.au.repository.InventoryDetailRepository;
import com.sl.au.repository.InvoiceDetailInfoRepository;
import com.sl.au.repository.InvoiceTotalInfoRepository;
import com.sl.au.repository.UserRepository;
import com.sl.au.service.ExcelService;
import com.sl.au.service.InvoiceTotalInfoService;
import com.sl.au.service.OperateLogService;
import com.sl.au.service.QueryService;

@Service("InvoiceTotalInfoService")
@Transactional
public class InvoiceTotalInfoServiceImpl extends BaseServiceImpl implements InvoiceTotalInfoService {

	@Autowired
	InvoiceTotalInfoRepository invoiceTotalInfoRepository;
	@Autowired
	InventoryDetailRepository invoiceDetailinfoRepository;
	@Autowired
	QueryService queryService;
	@Autowired
	OperateLogService operateLogService;
	@Autowired
	InvoiceDetailInfoRepository invoiceDetailInfoRepository;
	@Autowired
	CustomerRepository customerRepository;
	@Autowired
	UserRepository userRepository;
	@Autowired
	ContractInfoRepository contractInfoRepository;
	@Autowired
	AaccountsReceivableAccorspandingContractRepository Aaccounts;
	@Autowired
	ExcelService excelService;

	@Override
	public InvoiceTotalInfoRepository getRepository() {
		// TODO Auto-generated method stub
		return this.invoiceTotalInfoRepository;
	}

	@Override
	public List<InvoiceTotalInfo> findAllBykey(int start, int length, String key) {
		// TODO Auto-generated method stub
		Pageable pageable = new PageRequest(start / length, length, Sort.Direction.DESC, "createTime");
		Page<InvoiceTotalInfo> invoiceTotalInfos = invoiceTotalInfoRepository.findAllBykey(key, pageable);
		return invoiceTotalInfos.getContent();
	}

	@Override
	public long findAllBykeyCount(String key) {
		// TODO Auto-generated method stub
		return this.invoiceTotalInfoRepository.findAllBykeyCount(key);
	}

	@Override
	public List<InvoiceTotalInfo> findByIds(String ids) {
		// TODO Auto-generated method stub
		StringBuilder hql = buildCombinedQueryHql("InvoiceTotalInfo", "id", ids, "createTime", "desc");
		Query query = queryService.createQueryHql(hql.toString());
		System.out.println(hql.toString());
		@SuppressWarnings("unchecked")
		List<InvoiceTotalInfo> InvoiceTotalInfos = query.getResultList();
		return InvoiceTotalInfos;
	}

	public StringBuilder buildCombinedQueryHql(String entityName, String selectedProperty, String ids, String orderName,
			String dir) {
		StringBuilder hql = new StringBuilder();
		hql.append("select e from " + entityName + " e where e.id is not null ");
		hql.append(" and e." + selectedProperty + " in (" + ids + ")");
		hql.append(" order by " + orderName + " " + dir);
		return hql;
	}

	@Override
	public int delete(List<InvoiceTotalInfo> invoiceTotalInfoList, User user) {
		// TODO Auto-generated method stub
		String content = "";
		int dbool = 1;
		if (invoiceTotalInfoList.size() <= 0 || invoiceTotalInfoList == null) {
			dbool = 0;
		}
		List<List<InvoiceDetailInfo>> invoiceDetailInfos = new ArrayList<>();
		for (InvoiceTotalInfo invoiceTotalInfo : invoiceTotalInfoList) {
			List<InvoiceDetailInfo> newInfos = invoiceDetailInfoRepository
					.findAllBysInvoiceTotalId(invoiceTotalInfo.getId());
			if (newInfos.size() > 0 && newInfos != null) {
				invoiceDetailInfos.add(newInfos);
			}
		}
		for (InvoiceTotalInfo invoiceTotalInfo : invoiceTotalInfoList) {
			if (invoiceDetailInfos.size() > 0) {
				dbool = 0;
				return dbool;
			} else {
				SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd HH:mm:ss");
				BigDecimal bigDecimal = new BigDecimal(invoiceTotalInfo.getnInvoiceActualPrice());
				String time = null;
				// if(invoiceTotalInfo.getdInvoiceDate()!=null) time =
				// formatter.format(invoiceTotalInfo.getdInvoiceDate());
				time = formatter.format(invoiceTotalInfo.getdInvoiceDate());
				content += "删除总开票信息【" + "发票名称:" + invoiceTotalInfo.getsInvoiceName() + ",客户名称:"
						+ invoiceTotalInfo.getsInvoiceCustomerName() + ",金额:" + bigDecimal.toString() + ",时间:" + time
						+ "】;";
				invoiceTotalInfoRepository.delete(invoiceTotalInfo);
				dbool = 1;
			}

		}
		if (content != "") {
			content = content.substring(0, content.length() - 1);
			content += ".";
			operateLogService.log(user, "总开票删除", content);
		} else {
			dbool = 0;
		}
		return dbool;
	}

	@SuppressWarnings("unchecked")
	@Override
	@Transactional(propagation = Propagation.REQUIRED)
	public String importExcel(String fileName, User user) {
		String count = "";
		if (!StringUtils.hasText(fileName))
			return count;
		Map<String, Object> collections = new HashMap<>();
		// excelService.setStorageLocation(CRM.getStorageLocation());

		excelService.importExcel("invoiceTotalInfo", collections, fileName);
		if (collections.size() < 1 || collections.get("items") == null)
			return count;
		List<InvoiceTotalInfoFictitious> rows = (List<InvoiceTotalInfoFictitious>) collections.get("items");
		List<InvoiceTotalInfo> InvoiceTotalInfos = new ArrayList<InvoiceTotalInfo>();
		if (null != rows && rows.size() > 0) {
			for (int i = 0; i < rows.size(); i++) {
				InvoiceTotalInfoFictitious Invoice = rows.get(i);
				InvoiceTotalInfo newInvoice = new InvoiceTotalInfo();
				newInvoice.setsInvoiceIdentifyType(Invoice.getsInvoiceIdentifyType());
				if (!Invoice.getsInvoicePeopleId().equals("") && Invoice.getsInvoicePeopleId() != null) {
					String name = Invoice.getsInvoicePeopleId();
					List<User> users = userRepository.findByEmpName(name);
					// List<Option> options =
					// optionRepository.findByGroupAndTitle("凭证种类", title);
					if (users == null || users.size() < 1) {
						count = "第" + (i + 2) + "行的开票人不存在，请核实后导入。";
						return count;
					} else {
						newInvoice.setsInvoicePeopleId(users.get(users.size() - 1).getEmpLogin().getEmpId());
					}
				}
				if (!Invoice.getsInvoiceCustomerName().equals("") && Invoice.getsInvoiceCustomerName() != null) {
					String name = Invoice.getsInvoiceCustomerName();
					List<Customer> cus = customerRepository.findByCustomerName(name);
					if (cus == null || cus.size() < 1) {
						count = "第" + (i + 2) + "行的购方名称不存在，请核实后导入。";
						return count;
					} else {
						newInvoice.setsInvoiceCustomerName(cus.get(0).getCustomerName());
						newInvoice.setsInvoiceCustomerId(cus.get(0).getId());
					}
				}
				if (!Invoice.getdInvoiceDate().equals("") && Invoice.getdInvoiceDate() != null) {
					SimpleDateFormat formatter = new SimpleDateFormat("yyyy-MM-dd");
					try {
						Date d = formatter.parse(Invoice.getdInvoiceDate());
						newInvoice.setdInvoiceDate(d);
						newInvoice.setdInvoiceEffectiveDate(d);
					} catch (ParseException e) {
						count = "第" + (i + 2) + "行的时间格式不正确，请修改后导入。";
						return count;
					}
				}
				String s = Invoice.getnInvoiceActualPrice();
				String z = Invoice.getHjse();
				if ((!s.equals("") && s != null) || (!z.equals("") && z != null)) {
					/*
					 * Pattern pattern = Pattern.compile("^[0-9]*$"); boolean a
					 * = pattern.matcher(s).matches(); boolean b =
					 * pattern.matcher(z).matches(); if (a && b) {
					 */
					try {
						newInvoice.setnInvoiceActualPrice(Double.valueOf(s) + Double.valueOf(z));
					} catch (NumberFormatException e) {
						count = "第" + (i + 2) + "行的合计金额或者合计税额不是小数，请修改后导入。";
						return count;
					}
					/*
					 * } else { count = "第" + (i+2) +
					 * "行的合计金额或者合计税额不是小数，请修改后导入。"; return count; }
					 */
				}
				String rateValues = Invoice.getRateValue();
				String[] rateValue = rateValues.split("%");
				if (!rateValue[0].equals("") && rateValue[0] != null) {
					/*
					 * Pattern pattern = Pattern.compile("^[0-9]*$"); boolean a
					 * = pattern.matcher(s).matches(); boolean b =
					 * pattern.matcher(z).matches(); if (a && b) {
					 */
					try {
						newInvoice.setRateValue(Double.valueOf(rateValue[0]));
					} catch (NumberFormatException e) {
						count = "第" + (i + 2) + "行的税率不是小数，请修改后导入。";
						return count;
					}
					/*
					 * } else { count = "第" + (i+2) +
					 * "行的合计金额或者合计税额不是小数，请修改后导入。"; return count; }
					 */
				}
				if (!Invoice.getcController().equals("") && Invoice.getcController() != null) {
					String controller = Invoice.getcController();
					String[] aa = controller.split("\\\\|/");
					newInvoice.setcController(aa[0]);
				}
				newInvoice.setsInvoiceIdentify(Invoice.getsInvoiceIdentify());
				// newInvoice.setsInvoiceName(Invoice.getsInvoiceName());
				// newInvoice.setsInvoiceAccount(Invoice.getsInvoiceAccount());
				newInvoice.setsInvoiceCustomerAccount(Invoice.getsInvoiceCustomerAccount());
				// newInvoice.setsInvoiceTradeType(Invoice.getsInvoiceTradeType());
				newInvoice.setsInvoiceMemo(Invoice.getsInvoiceMemo());
				newInvoice.setsCreateUserId(user.getEmpLogin().getEmpId());
				InvoiceTotalInfos.add(newInvoice);
			}
			this.invoiceTotalInfoRepository.save(InvoiceTotalInfos);
			count = "成功导入" + rows.size() + "条数据。";
			importInvoiceDetailInfo(user);

		}
		return count;
	}

	public void importInvoiceDetailInfo(User user) {
		List<InvoiceTotalInfo> invoiceTotalInfos = invoiceTotalInfoRepository.findByCController();
		for (InvoiceTotalInfo i : invoiceTotalInfos) {
			if (i.getcController().equals("") || i.getcController() != null) {
				ContractInfo contractInfo = contractInfoRepository.findBySupplierCode(i.getcController());
				if (contractInfo != null) {
					float[] paymentSum = invoiceDetailInfoRepository.getPaymentSum(contractInfo.getContractId());
					float sums = 0;
					for (int j = 0; j < paymentSum.length; j++) {
						sums = sums + paymentSum[j];
					}
					if (contractInfo.getTotalSum() - sums > 0) {
						InvoiceDetailInfo inventoryDetail = new InvoiceDetailInfo();
						inventoryDetail.setsCreateUserId(user.getEmpLogin().getEmpId());
						inventoryDetail.setsInvoiceTotalId(i);
						inventoryDetail.setsContractId(contractInfo.getContractId());
						inventoryDetail.setsContractType(contractInfo.getContractType());
						inventoryDetail.setsInvoicePersonId(i.getsInvoicePeopleId());
						inventoryDetail.setdInvoicePlanAccDate(i.getdInvoiceDate());
						// inventoryDetail.setdInvoiceActualAccDate(i.getdInvoiceDate());
						inventoryDetail.setnInvoiceTaxRate(17);
						inventoryDetail.setnInvoiceTaxPrice(0);
						inventoryDetail.setsInvoiceMemo(i.getsInvoiceMemo());
						if (i.getnInvoiceActualPrice() < contractInfo.getTotalSum() - sums) {
							inventoryDetail.setnInvoiceDetailPrice(i.getnInvoiceActualPrice());
						} else {
							inventoryDetail.setnInvoiceDetailPrice(contractInfo.getTotalSum() - sums);
						}
						invoiceDetailInfoRepository.save(inventoryDetail);
						AaccountsReceivableAccorspandingContract aaccountsReceivableAccorspandingContract = Aaccounts
								.findBySContractIdAndSContractTypeAndNContractOrgType(inventoryDetail.getsContractId(),
										inventoryDetail.getsContractType(), 2);
						if (aaccountsReceivableAccorspandingContract == null) {
							AaccountsReceivableAccorspandingContract newAaccountsReceivableAccorspandingContract = new AaccountsReceivableAccorspandingContract();
							newAaccountsReceivableAccorspandingContract.setnContractOrgType(2);
							newAaccountsReceivableAccorspandingContract.setnIsUpdate(0);
							newAaccountsReceivableAccorspandingContract.setnIsUpdateForTotal(0);
							newAaccountsReceivableAccorspandingContract
									.setsContractId(inventoryDetail.getsContractId());
							newAaccountsReceivableAccorspandingContract
									.setsContractType(inventoryDetail.getsContractType());
							Aaccounts.save(newAaccountsReceivableAccorspandingContract);
						} else {
							aaccountsReceivableAccorspandingContract.setnContractOrgType(2);
							aaccountsReceivableAccorspandingContract.setnIsUpdate(0);
							aaccountsReceivableAccorspandingContract.setnIsUpdateForTotal(0);
							aaccountsReceivableAccorspandingContract.setsContractId(inventoryDetail.getsContractId());
							aaccountsReceivableAccorspandingContract
									.setsContractType(inventoryDetail.getsContractType());
							Aaccounts.save(aaccountsReceivableAccorspandingContract);
						}
					}
				}
				i.setcController(null);
				invoiceTotalInfoRepository.save(i);
			}
		}
	}

}
